import { ErrorText } from "../enums/ErrorEnums"

/**
 * 商品实体 - 包含商品的核心属性和行为
 * 在DDD中，实体具有唯一标识和生命周期
 */
export class Product {
    private readonly _id: number;
    private _name: string;
    private _description: string;
    private _price: number;
    private _imageUrl: string;
    private _stock: number;
    private _categoryId: number;

    constructor(
        id: number,
        name: string,
        description: string,
        price: number,
        imageUrl: string,
        stock: number,
        categoryId: number,
    ) {
        this._id = id;
        this._name = name;
        this._description = description;
        this._price = price;
        this._imageUrl = imageUrl;
        this._stock = stock;
        this._categoryId = categoryId;
    }

    // 实体唯一标识
    get id(): number {
        return this._id;
    }

    public get name(): string {
        return this._name;
    }
    public set name(value: string) {
        this._name = value;
    }

    public get description(): string {
        return this._description;
    }
    public set description(value: string) {
        this._description = value;
    }


    public get price(): number {
        return this._price;
    }
    public set price(value: number) {
        if (value < 0) {
            throw new Error(ErrorText.PriceNotNegativein);
        }
        this._price = value;
    }

    public get imageUrl(): string {
        return this._imageUrl;
    }
    public set imageUrl(value: string) {
        this._imageUrl = value;
    }

    public get stock(): number {
        return this._stock;
    }
    public set stock(value: number) {
        if (value < 0) {
            throw new Error(ErrorText.StockNotNegativein)
        }
        this._stock = value;
    }

    public get categoryId(): number {
        return this._categoryId;
    }
    public set categoryId(value: number) {
        this._categoryId = value;
    }

    /**
     * 检查商品是否有库存
     */
    hasStock() {
        return this._stock > 0
    }

    /**
     * 减少商品库存
     * @param quantity 减少的数量
     */
    reduceStock(quantity: number): void {
        if (quantity <= 0) {
            throw new Error(ErrorText.StockIsGreaterThanZero)
        }

        if (this._stock < quantity) {
            throw new Error(ErrorText.LowStock)
        }

        this._stock -= quantity;
    }

    /**
     * Class类转化为普通json数据
     */
    toDTO(): Record<string, string | number> {
        return {
            id: this._id,
            name: this._name,
            description: this._description,
            price: this._price,
            imageUrl: this._imageUrl,
            stock: this._stock,
            categoryId: this._categoryId
        }
    }

    /**
     * 从json数据创建Product类实例
     * 转化为领域实体 Product
     */
    static fromDTO(data: Record<string, any>): Product {
        return new Product(
            data.id,
            data.name,
            data.description,
            data.price,
            data.imageUrl,
            data.stock,
            data.categoryId,
        );
    }
}